﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ComponentModel;

namespace Kokomo.Mirror.CliMetadata
{
	abstract class MetadataRowPropertyDescriptor : PropertyDescriptor
	{
		public static PropertyDescriptor GetPropertyDescriptor(
			PropertyDescriptor baseDescriptor,
			MetadataContainer container
			)
		{
			if (baseDescriptor == null) throw new ArgumentNullException("baseDescriptor");
			if (container == null) throw new ArgumentNullException("container");

			Type propertyType = baseDescriptor.PropertyType;

			PropertyDescriptor descriptor;
			if (propertyType == typeof(StringRef))
				descriptor = new StringRefPropertyDescriptor(baseDescriptor, container);
			else if (propertyType == typeof(BlobRef))
				descriptor = new BlobRefPropertyDescriptor(baseDescriptor, container);
			else if (propertyType == typeof(SignatureRef))
				descriptor = new SignatureRefPropertyDescriptor(baseDescriptor, container);
			else if (propertyType == typeof(CodedIndex))
				descriptor = new CodedIndexPropertyDescriptor(baseDescriptor, container);
			else
				descriptor = baseDescriptor;

			return descriptor;
		}

		public MetadataRowPropertyDescriptor(
			PropertyDescriptor baseDescriptor,
			MetadataContainer container
			)
			: base(baseDescriptor)
		{
			if (container == null) throw new ArgumentNullException("container");
			if (baseDescriptor == null) throw new ArgumentNullException("baseDescriptor");

			this.Container = container;
			this.BaseDescriptor = baseDescriptor;
		}

		public PropertyDescriptor BaseDescriptor { get; private set; }
		public MetadataContainer Container { get; private set; }

		public override bool CanResetValue(object component)
		{
			return this.BaseDescriptor.CanResetValue(component);
		}

		public override Type ComponentType
		{
			get { return this.BaseDescriptor.ComponentType; }
		}

		public override bool IsReadOnly
		{
			get { return this.BaseDescriptor.IsReadOnly; }
		}

		public override void ResetValue(object component)
		{
			this.BaseDescriptor.ResetValue(component);
		}

		public override void SetValue(object component, object value)
		{
			this.BaseDescriptor.SetValue(component, value);
		}

		public override bool ShouldSerializeValue(object component)
		{
			return this.ShouldSerializeValue(component);
		}
	}
}
